package com.alstudio.utils.android.media.audio.recorder;

import android.view.Gravity;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnTouchListener;
import android.widget.PopupWindow.OnDismissListener;

import com.alstudio.app.ALLocalEnv;
import com.alstudio.pojo.module.server.Serverlet;
import com.alstudio.ui.base.BaseActivity;
import com.alstudio.utils.activity.ALActivityManager;
import com.alstudio.utils.activity.ALActivityManager.ActivityLifeCycleListener;
import com.alstudio.utils.android.ALFileManager;
import com.alstudio.utils.android.ALSdcardManager;
import com.alstudio.utils.android.media.audio.player.ALAudioPlayTask;
import com.alstudio.utils.android.media.audio.player.ALAudioPlayTask.ALAudioPlayTaskCallback;
import com.alstudio.utils.android.media.audio.recorder.ALAudioRecorder.ALAudioRecordErroCode;
import com.alstudio.utils.android.net.download.ALHttpDownloadTask.ALHttpDownloadErrorCode;
import com.alstudio.utils.android.net.http.http2.UploadMediaRequest.MediaUploadCallback;
import com.alstudio.utils.android.net.uploader.ALHttpUploadTaskManager;
import com.alstudio.utils.log.ALLog;
import com.alstudio.view.popwindow.ALPopWindowUtils;
import com.alstudio.view.toast.MyToastUtil;
import com.loovee.imaohu.R;

public class ALAudioRecordTask implements ALAudioRecordCallback,
		ALAudioPlayTaskCallback, OnDismissListener, ActivityLifeCycleListener {

	private ALAudioRecordTaskInfo info;

	private BaseActivity mContext;

	private ALAudioRecorder mRecord;

	private ALAudioPlayTask mPlayTask;

	private final String SUFIX = ".amr";

	private final String DEFAULT_SAVE_PATH = ALSdcardManager
			.getExtStoragePath();
	// 最大录音时间为5分钟
	private final int DEFAULT_MAX_DURATION = 300 * 1000;

	private int mxa_duration = DEFAULT_MAX_DURATION;

	private String savePath = DEFAULT_SAVE_PATH;

	private String filePath;

	private String fileName;

	private long startTime = 0;

	private boolean isRecallRequest = false;

	private String mTimerFormat;

	private int recordSecond = 0;

	private ALAudioRecordTaskCallback mSaveCallback;

	/********************************************************/
	// 需要录制AAC音频
	private boolean isRecordingAacRequest = false;
	// AAC音频录制
	private String aacFilePath;
	// AAC音频录制
	// private AdtsMixRecoder aacRecorder;

	/********************************************************/

	private boolean isAutoProccess = true;
	private boolean isAutoDismissRequest = true;

	private MediaUploadCallback mediaUploadCallback;

	public ALAudioRecordTask(BaseActivity context) {
		// TODO Auto-generated constructor stub
		mContext = context;
		info = ALPopWindowUtils.showRecordWindow(mContext, true);
		initTask();
	}

	public ALAudioRecordTask(BaseActivity context,
			ALAudioRecordTaskCallback audioSaveCallback) {
		// TODO Auto-generated constructor stub
		this(context);
		mSaveCallback = audioSaveCallback;
	}

	/**
	 * @param mediaUploadCallback
	 *            the mediaUploadCallback to set
	 */
	public void setMediaUploadCallback(MediaUploadCallback mediaUploadCallback) {
		this.mediaUploadCallback = mediaUploadCallback;
	}

	/**
	 * @return the mediaUploadCallback
	 */
	public MediaUploadCallback getMediaUploadCallback() {
		return mediaUploadCallback;
	}

	public void setSecondInfo(String info) {
		this.info.setSecondInfo(info);
	}

	// 设置右边按钮名
	public void setPostiveButtonName(String name) {
		this.info.setPostiveButtonName(name);
	}

	// 设置左边按钮名
	public void setNegativeButtonName(String name) {
		this.info.setNegativeButtonName(name);
	}

	public void setMaxDuration(int max_duration_ms) {
		this.mxa_duration = max_duration_ms;
	}

	public int getMaxDuration() {
		return mxa_duration;
	}

	public void dismiss() {
		if (info != null && info.getWindow() != null) {
			info.getWindow().dismiss();
		}
	}

	public boolean isShowing() {
		if (info != null) {
			return info.getWindow().isShowing();
		}
		return false;
	}

	public void setAutoProccess(boolean isAutoProccess) {
		this.isAutoProccess = isAutoProccess;
	}

	public boolean isAutoProccess() {
		return isAutoProccess;
	}

	public boolean isAutoDismissRequest() {
		return isAutoDismissRequest;
	}

	public void setAutoDismissRequest(boolean isAutoDismissRequest) {
		this.isAutoDismissRequest = isAutoDismissRequest;
	}

	private void initTask() {
		// 播放按钮监听器
		if (info.getPlayView() != null) {
			info.getPlayView().setOnClickListener(playListener);
		}

		// 重录按钮监听器
		if (info.getPressToRecallView() != null) {
			info.getPressToRecallView().setOnClickListener(
					pressToRecallListener);
		}

		// 保存按钮监听器
		if (info.getPressToSaveView() != null) {
			info.getPressToSaveView().setOnClickListener(pressToSaveListener);
		}

		// 关闭按钮监听器
		if (info.getCloseIconView() != null) {
			info.getCloseIconView().setOnClickListener(iconCloseListener);
		}

		// 按住说话按钮
		if (info.getPressToTalkView() != null) {
			info.getPressToTalkView().setOnTouchListener(pressToTalkListener);
		}

		info.getWindow().setOnDismissListener(this);

		mTimerFormat = mContext.getResources().getString(
				R.string.TxtAudioRecordTimeFormat);

		ALActivityManager.getALActivityManager().setActivityLifeCycleListener(
				this);
	}

	private void showPressToTalkButton() {
		showView(info.getPressToTalkView());

	}

	private void hidePressToTalkButton() {
		hideView(info.getPressToTalkView());

	}

	private void showPressToSaveButtonLayout() {
		showView(info.getSaveButtonLayout());

	}

	private void hidePressToSaveButtonLayout() {
		hideView(info.getSaveButtonLayout());
	}

	private void showPlayButton() {
		showView(info.getPlayView());
		// setViewBackground(info.getPlayView(),
		// R.drawable.bomb_botton_play_selector);
	}

	private void resetRecordTime() {
		String timeStr = String.format(mTimerFormat, recordSecond / 60,
				recordSecond % 60);

		info.getRecordTimeView().setText(timeStr);

		// info.getRecordTimeView().setText(""+recordSecond);
	}

	private void hidePlayButton() {
		hideView(info.getPlayView());
	}

	private void showStopButton() {
		showView(info.getPlayView());
		// setViewBackground(info.getPlayView(),
		// R.drawable.bomb_botton_stop_selector);
	}

	private void hideStopButton() {
		hideView(info.getPlayView());
	}

	private void updateRecordingBeat(int percent) {
		info.getRecordingBeatView().setProgress(percent);
	}

	private void updateAudioTime(int time) {

		String timeStr = String.format(mTimerFormat, time / 60, time % 60);

		info.getRecordTimeView().setText(timeStr);
	}

	private void resetAudioTime() {
		info.getRecordTimeView().setText("00:00");
	}

	public void showRecordWindow(View parent) {
		if (parent != null) {
			info.getWindow().showAtLocation(parent, Gravity.CENTER_VERTICAL, 0,
					0);
			if (mSaveCallback != null) {
				mSaveCallback.onWindowShowed();
			}
			isRecallRequest = false;
		}
	}

	public void release() {
		mRecord = null;
		mPlayTask = null;
		// aacRecorder = null;
		// ActivityManager.getActivityManager().setActivityLifeCycleListener(null);
	}

	public void setSaveCallback(ALAudioRecordTaskCallback callback) {
		mSaveCallback = callback;
	}

	public void resetView() {
		isRecallRequest = true;
		// 关闭播放
		reseatPlayer();
		resetAudioTime();
		// 隐藏重录、保存布局
		hidePressToSaveButtonLayout();
		// 显示按住说话布局
		showPressToTalkButton();
		// 隐藏播放按钮
		hidePlayButton();
		filePath = "";
		fileName = "";
	}

	@Override
	public void onRecording() {
		// TODO Auto-generated method stub
		ALLog.d("开始录音");
		recordSecond = 0;
		updateAudioTime(0);
	}

	@Override
	public void onRecordStop() {
		// TODO Auto-generated method stub
		ALLog.d("录音结束");
		doRecordDone();
	}

	@Override
	public void onAudioError(ALAudioRecordErroCode code) {
		// TODO Auto-generated method stub
		ALLog.d("录音错误 " + code);
		recordSecond = 0;
		resetAudioTime();
	}

	@Override
	public void onAudioAmplitudeChanged(int ratio) {
		// TODO Auto-generated method stub
		ALLog.d("起始录音强度为" + ratio);
		ratio = ratio * 100 / 32768;
		if (ratio > 100) {
			ratio = 100;
		}
		ALLog.d("录音强度为" + ratio);
		updateRecordingBeat(ratio);
	}

	@Override
	public void onAudioProgressChanged(int second) {
		// TODO Auto-generated method stub
		ALLog.d("录音时常变化: " + second);
		recordSecond = second;
		updateAudioTime(second);
	}

	@Override
	public void onAudioMaxDurationReached() {
		// TODO Auto-generated method stub
		ALLog.d("已达录音时长");

	}

	private void showView(View v) {
		if (v != null) {
			v.setVisibility(View.VISIBLE);
		}
	}

	private void hideView(View v) {
		if (v != null) {
			v.setVisibility(View.GONE);
		}
	}

	private void setViewBackground(View v, int res) {
		if (v != null) {
			v.setBackgroundResource(res);
		}
	}

	private OnClickListener iconCloseListener = new OnClickListener() {

		@Override
		public void onClick(View v) {
			// TODO Auto-generated method stub
			if (info.getWindow() != null) {
				info.getWindow().dismiss();
			}
		}
	};

	private OnClickListener pressToRecallListener = new OnClickListener() {

		@Override
		public void onClick(View v) {
			// TODO Auto-generated method stub
			resetView();
		}
	};

	private OnClickListener pressToSaveListener = new OnClickListener() {

		@Override
		public void onClick(View v) {
			// TODO Auto-generated method stub
			doSave();
		}
	};

	private void doSave() {
		reseatPlayer();

		if (isAutoProccess) {

			ALAudioRecordManager.saveAudioPath(filePath);

			// 录音长度
			ALAudioRecordManager.setAudioLen(recordSecond);

			if (ALLocalEnv.isNetworkConnected()) {
				// 開始上傳
				String servletUrl = Serverlet
						.getUploadServerUrl(Serverlet.UPLOAD_AUDIO_SERVERLET);

				ALHttpUploadTaskManager.UploadVoiceIntroRequest(servletUrl,
						filePath, mediaUploadCallback);
			} else {
				// 无网络
				ALAudioRecordManager.setUploadAudioState(true);
			}
		} else {
			ALLocalEnv.isNetworkConnected();
		}

		if (mSaveCallback != null) {
			mSaveCallback.onAudioSaved(filePath, recordSecond);
		}

		if (isAutoDismissRequest) {
			info.getWindow().dismiss();
		}
	}

	private OnClickListener playListener = new OnClickListener() {

		@Override
		public void onClick(View v) {
			// TODO Auto-generated method stub
			doPlay();
		}
	};

	private void doPlay() {
		if (mPlayTask != null) {
			if (mPlayTask.isPlaying()) {
				mPlayTask.stop();
				mPlayTask = null;
			}
		} else {
			mPlayTask = new ALAudioPlayTask(mContext, filePath,
					ALAudioRecordTask.this);
			mPlayTask.Play();
		}
	}

	private void reseatPlayer() {
		if (mPlayTask != null) {
			if (mPlayTask.isPlaying()) {
				mPlayTask.stop();
			}
			mPlayTask = null;
		}
	}

	// private OnClickListener pressToTalkListener = new OnClickListener() {
	//
	// @Override
	// public void onClick(View v) {
	// // TODO Auto-generated method stub
	// doPressToTalk();
	// }
	// };

	private void doPressToTalk() {
		doRecordStart();
	}

	private OnTouchListener pressToTalkListener = new OnTouchListener() {

		@Override
		public boolean onTouch(View v, MotionEvent event) {
			// TODO Auto-generated method stub
			doPressToTalk(event.getAction());
			return false;
		}
	};

	private void doPressToTalk(int event) {
		switch (event) {
		case MotionEvent.ACTION_DOWN:
			doRecordStart();
			break;
		case MotionEvent.ACTION_UP:
		case MotionEvent.ACTION_CANCEL:
			doRecordDone();
			break;
		}
	}

	private void doRecordStart() {
		if (ALSdcardManager.isExtStorageAvailable()) {

			if (!ALFileManager.isFileExsit(savePath)) {
				ALFileManager.createFile(savePath);
			}
			filePath = null;
			aacFilePath = null;

			String fileName = System.currentTimeMillis() + SUFIX;

			this.fileName = fileName;

			startTime = System.currentTimeMillis();

			if (isRecordingAacRequest) {
				// 需要录制为AAC
				if (!savePath.endsWith("/")) {
					savePath += "/";
				}
				this.aacFilePath = savePath + "aac" + fileName;
				// aacRecorder = new AdtsMixRecoder(aacFilePath,
				// ALAudioRecordTask.this);
				// aacRecorder.setMaxDuration(mxa_duration);
				// aacRecorder.startWorking();
			} else {
				mRecord = new ALAudioRecorder(mContext, savePath, fileName,
						mxa_duration, ALAudioRecordTask.this);
				mRecord.start();
			}
			updateAudioTime(0);
		}
	}

	private void doRecordDone() {
		if (mRecord != null) {
			filePath = mRecord.getFilePath();
			mRecord.stop();
			mRecord = null;
		}

		// if (aacRecorder != null) {
		// aacRecorder.stopWorking();
		// aacRecorder = null;
		// }

		if (isRecordingAacRequest) {
			if (ALFileManager.isFileExsit(aacFilePath)) {
				filePath = aacFilePath;
				ALLog.d("播放AAC文件");
			}
		}

		// 进度恢复为0
		updateRecordingBeat(0);

		long endTime = System.currentTimeMillis();
		if ((endTime - startTime) / 1000 > 1) {
			// 显示重录、保存布局
			showPressToSaveButtonLayout();
			// 隐藏按住说话布局
			hidePressToTalkButton();
			// 显示播放按钮
			showPlayButton();

			isRecallRequest = false;
		} else {
			// 录音时长太短
			MyToastUtil.getInstance().showToastOnCenter(
					mContext.getString(R.string.TxtAudioTimeTooShort));
			resetAudioTime();
		}
	}

	/************************************************ 以下为语音播放回调 **********************************************************/

	@Override
	public void onMusicPlay() {
		// TODO Auto-generated method stub
		updateAudioTime(0);
		showStopButton();
		// resetRecordTime();
	}

	@Override
	public void onMusicStop() {
		// TODO Auto-generated method stub
		if (isRecallRequest) {
			isRecallRequest = false;
			return;
		}
		showPlayButton();
		reseatPlayer();
		resetRecordTime();
	}

	@Override
	public void onMusicPause() {
		// TODO Auto-generated method stub

	}

	@Override
	public void onMusicError() {
		// TODO Auto-generated method stub
		showPlayButton();
		resetRecordTime();
	}

	@Override
	public void onMusicProgressChanged(int second) {
		// TODO Auto-generated method stub
		updateAudioTime(second);
	}

	@Override
	public void onUpdateProcess(int percent) {
		// TODO Auto-generated method stub

	}

	@Override
	public void onDownloadFinish(String path) {
		// TODO Auto-generated method stub

	}

	@Override
	public void onPreDownload() {
		// TODO Auto-generated method stub

	}

	@Override
	public void onDownloadFail(ALHttpDownloadErrorCode code) {
		// TODO Auto-generated method stub

	}

	/************************************************************** 以下为对话框消失回调 **************************************************************************/
	private void doWindowClose() {

		if (mSaveCallback != null) {
			mSaveCallback.onWindowDismissed();
		}

		resetView();
		reseatPlayer();

		mContext.exitBlur();

		if (mRecord != null) {
			if (mRecord.isRecording()) {
				mRecord.stop();
			}
			mRecord = null;
		}

		// if (aacRecorder != null) {
		// aacRecorder.stopWorking();
		// aacRecorder = null;
		// }
	}

	@Override
	public void onDismiss() {
		// TODO Auto-generated method stub
		doWindowClose();
	}

	/*********************************************************************** 以下为界面状态变化,当界面onPuase时，关闭播放 *************************************************************************************/

	@Override
	public void onActivityCreate(BaseActivity actvity) {
		// TODO Auto-generated method stub

	}

	@Override
	public void onActivityStart(BaseActivity actvity) {
		// TODO Auto-generated method stub

	}

	@Override
	public void onActivityResume(BaseActivity actvity) {
		// TODO Auto-generated method stub

	}

	@Override
	public void onActivityPause(BaseActivity actvity) {
		// TODO Auto-generated method stub
		reseatPlayer();
		if (recordSecond > 0) {
			updateAudioTime(recordSecond);
		}
	}

	@Override
	public void onActivityStop(BaseActivity actvity) {
		// TODO Auto-generated method stub

	}

	@Override
	public void onActivityFinish(BaseActivity actvity) {
		// TODO Auto-generated method stub
		release();
	}

	@Override
	public void onActivityDestroy(BaseActivity actvity) {
		// TODO Auto-generated method stub

	}

	public interface ALAudioRecordTaskCallback {
		public void onAudioSaved(String path, int audioLen);

		public void onWindowShowed();

		public void onWindowDismissed();
	}

}
